package com.sxt.service.impl;


import javax.annotation.PostConstruct;
import javax.jms.JMSException;
import javax.jms.Message;
import javax.jms.MessageListener;
import javax.jms.ObjectMessage;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.jms.annotation.JmsListener;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;

import com.sxt.model.WechatMsg;
import com.sxt.service.WechatNotifyService;

import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONUtil;

@Service
public class WechatNotifyServiceImpl implements WechatNotifyService ,MessageListener {

	@Autowired
	private RestTemplate rest; // 该对象在spring-web 里面，我们没有依赖它，所以没有

	private static final Logger log = LoggerFactory.getLogger(WechatNotifyServiceImpl.class) ;
	
	private static final String MESSAGE_URL = "https://api.weixin.qq.com/cgi-bin/message/template/send?access_token=%s" ;

	private static final String TOKEN_URL = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=%s&secret=%s" ;

	@Value("${wechat.appId}")
	private String appId;

	@Value("${wechat.secret}")
	private String secret ;
	/**
	 * 2 个小时过期一次
	 * 1 项目启动获取一次
	 * 2 以后每个2 个小时获取一次
	 */
	private String accessToken ;

	/**
	 * TOKEN的获取
	 * GET https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=APPID&secret=APPSECRET
	 */
	@PostConstruct
	public void initToken() {
		refreshToken();
	}

	@Scheduled(initialDelay = 7100*1000,fixedDelay = 7100*1000) // 该方法只要项目启动，就能执行，但是它的执行时机较慢，可能我们的系统一启动就需要发送消息，只要@PostConstruct 是最先启动
	public void refreshToken() {
		String jsonResult = rest.getForObject(String.format(TOKEN_URL, appId ,secret), String.class) ;
		JSONObject parseObj = JSONUtil.parseObj(jsonResult) ;
		if(parseObj.containsKey("access_token")) {
			accessToken = parseObj.getStr("access_token") ;
		}else {
			System.out.println(parseObj);
		}
	}

	/**
	 * 消息监听器监听到了消息
	 * @param message
	 */
	@JmsListener(destination = "wechat.msg.queue") // 监听某个队列
	public void onMessage(Message message) {
		ObjectMessage  objectMsg = (ObjectMessage) message ; 
		WechatMsg wechatMsg;
		try {
			wechatMsg = (WechatMsg)objectMsg.getObject();// 从对象消息里面得到我们的参数
			sendMsg(wechatMsg); // 发送  消息
		} catch (JMSException e) {
			log.error("发送微信消息时，有错误{}", e.getCause());
			e.printStackTrace();
		}
		
	}

	
	
	@Override
	public void sendMsg(WechatMsg message) {

		/**
		 * 我们发送的是json 对象
		 * 但是RestTemplate 底层会将对象->json(jackson)
		 * 
		 */
		String postForObject = rest.postForObject(String.format(MESSAGE_URL, accessToken), message, String.class);
		System.out.println(postForObject);

	}
	//	public static void main(String[] args) {
	//		RestTemplate rest = new RestTemplate() ;
	//		WechatMsg wechatMsg = new WechatMsg();
	//		wechatMsg.setToUser("op16B0zbY0O-uMAMz1XVFE0yDxYI");
	//		wechatMsg.setUrl("www.whsxt.com");
	//		wechatMsg.setTemplateId("hXl1irH8oK_qOb5EL64XxMJnpF-UbkjeqlR9Kb5DvHc");
	//		wechatMsg.setTopColor("#FF0000");
	//		Map<String, Map<String, String>> data = new HashMap<String, Map<String,String>>();
	//		// 该死的：{{user.DATA}}，你的欠账信息有新的进度提醒！ 借款时间：{{date.DATA}} 借款金额：{{money.DATA}} 违例时间：{{endTime.DATA}} 截至{{now.DATA}}，你产生的利息已达{{lixi.DATA}} ,如果不按期归还，你将会进入失信名单！
	//		data.put("user", WechatMsg.builde("梁天东", ""));
	//		data.put("date", WechatMsg.builde("2016年12月25日", ""));
	//		data.put("money", WechatMsg.builde("30000.00", ""));
	//		data.put("endTime", WechatMsg.builde("2018年12月25日", ""));
	//		data.put("now", WechatMsg.builde("2020年1月3日", ""));
	//		data.put("lixi", WechatMsg.builde("800000.00", ""));
	//		wechatMsg.setData(data);
	//		String postForObject = rest.postForObject(String.format(MESSAGE_URL, "29_sMyy52k0QercJYu9woFw23jPcK0rfFsFfcNVmEGGs-7Dj4y2QNOiHUmO8IMUh4D1-zS41OLnDRGReCJjG6L_osyU3n7QhRG5z3X71neAKz7DCBpsPpDmrNgVp0bly_9GTpV0EjAHp4SS4hFgTHPhABAXLT"), wechatMsg, String.class);
	//		System.out.println(postForObject);
	//	}


}
